package com.lzy.cloud.order.service.impl;

import com.lzy.cloud.order.constants.OrderDistributePrefix;
import com.lzy.cloud.order.service.SerialNumberService;
import com.lzy.framework.core.cache.cluster.RedisClusterService;
import com.lzy.framework.core.ensure.Ensure;
import com.lzy.framework.core.lock.RedisGlobalLock;
import com.lzy.framework.tools.date.DateStyle;
import com.lzy.framework.tools.date.DateUtils;
import org.apache.commons.lang3.RandomStringUtils;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.util.concurrent.TimeUnit;

@Component("orderSerialNumberService")
public class SerialNumberServiceImpl implements SerialNumberService {

    private static final Logger LOGGER = LoggerFactory
            .getLogger(SerialNumberServiceImpl.class);

    @Autowired
    private RedisClusterService redisClusterService;

    @Autowired
    private RedisGlobalLock redisGlobalLock;

    /**
     * 订单号生成 生成规则： 3 + 业务000 + 时间月日0000 + 用户ID后四位0000 + 自增0000000（每天第一单100+ 随机四位数）
     *
     * @param biz 业务模块
     * @return
     * @throws Exception
     * @throws
     */
    @Override
    public Long createSerialNumber(String biz, String userId) {
        if (StringUtils.isBlank(biz) || StringUtils.isBlank(userId)) {
            return null;
        }
        if (redisGlobalLock.lock(biz, OrderDistributePrefix.LOCK_ORDER_TIME, TimeUnit.MILLISECONDS)) {
            try {
                String date = DateUtils.DateToString(null,
                        DateStyle.MMDD);
                String key = OrderDistributePrefix.ORDER_ID + biz
                        + date;// key
                String start = 3 + String.format("%03d", Long.parseLong(biz)) + date + returnStr(userId);

                String v = redisClusterService.get(key, String.class);
                String s = null;// value
                if (null == v) {// 每天第一次生成405231019919280
                    s = start + "100" + RandomStringUtils.random(4, false, true);
                    redisClusterService.set(key, s, Integer.MAX_VALUE);
                    return Long.valueOf(s);
                } else {
                    v = v.substring(
                            v.length() - 7,
                            v.length());
                    Integer returnInt = Integer.valueOf(v);
                    returnInt++;
                    v = start + returnInt;
                    redisClusterService.set(key, v, Integer.MAX_VALUE);
                    return Long.valueOf(v);
                }
            } catch (Exception e) {
                LOGGER.error("获取订单号失败", e);
                Ensure.that(e).isNotNull("08000007");
            } finally {
                redisGlobalLock.unlock(biz);
            }
        }
        return null;
    }

    private String returnStr(String userId) {
        int len = userId.length();
        String str = null;
        if (len >= 4) {
            str = userId.substring(len - 4);
        } else {
            String s = "";
            for (int i = 0; i < 4 - len; i++) {
                s = s + "0";
            }
            str = s + userId;
        }
        return str;
    }



}
